import { store, isIgnore, Stack } from "./consts.js";
import { get } from "./net-utils.js";

const renderContent = (filePath, content) => {
    // console.log(`prepare render:`, content)
    let contentText = Base64.decode(content);
    if (/\.md$/.test(filePath)) {
        $store.contentElement.innerHTML = $store.converter.makeHtml(contentText);
    } else {
        $store.contentElement.innerHTML = `<pre>${contentText}</pre>`;
    }
}
const renderTree = (filePath, treeData) => {
    let navHtml = `<ul onclick="dealTreeClick(event)" onmouseover="dealTreeHover(event)" onmouseout="dealTreeHover(event, 'leave')">`;

    if (store.navStack.length > 0) {
        navHtml = navHtml + `<li class="nav">&nbsp;<i class="fa fa-angle-left"></i>&nbsp;</li>`
    }
    if (treeData) {
        treeData.forEach(v => {
            // console.log('deal tree...', v)
            if (!isIgnore(v.path)) {
                store.navStore[v.path] = v;
                if (v.type === 'blob') {
                    navHtml += `<li class="blob">${v.path}</li>`
                } else {
                    navHtml += `<li class="tree">${v.path}</li>`
                }
            }
        })
    }
    navHtml = navHtml + "</ul>"
    $store.navElement.innerHTML = navHtml;
}

const previewBlob = (filePath) => {
    if (store.navStore[filePath]) {
        get(store.navStore[filePath].url).then(v => {
            renderContent(filePath, v.content);
        })
    } else {
        console.error("文件名异常，不存在!" + filePath)
    }
}

const previewTree = (filePath) => {
    if (store.navStore[filePath]) {
        let temp = store.navStore;

        store.navStack.push(Object.assign({}, store.navStore))
        store.navStore = {};
        get(temp[filePath].url).then(v => {
            renderTree(filePath, v.tree);
        })
    } else {
        console.error(`Directory name ${filePath} exception.`)
    }
}

const getKeyEle = (element, eleType) => {
    let ele = element;
    eleType = eleType.toUpperCase();
    for (;ele !== null && ele.tagName !== eleType; ele = ele.parentElement) {
        // console.log("ele:", ele);
    }
    if (ele === null) {
        throw new Error(`未找到 ${eleType} 元素`)
    }
    return ele;
}

const dealTreeClick = function (e) {
    e.stopPropagation()
    let keyElement = getKeyEle(e.target, "li");
    switch(keyElement.className) {
        case 'blob':
            previewBlob(keyElement.innerHTML);
            break;
        case 'tree':
            previewTree(keyElement.innerHTML)
            break;
        case 'nav':
            backNav();
            break;
        default:
            console.error(`type:${keyElement.className} not supported.`)
    }
}


const generatePosition = (rectList, type="bottom") => {
    let {left, top, bottom, right, width, height} = rectList;
    let topP = bottom;
    let leftP = left + width / 2;
    return {topP, leftP}
}
const elePositionUtil = (e) => {
    // console.log(e.getClientRects())
    // console.log(e.getBoundingClientRect())
    let rectList = e.getBoundingClientRect();
    return generatePosition(rectList);
}
const hoverSubMenuPosUtil = (pos, data) => {
    let rectArr = store.hoverSubMenu.getBoundingClientRect();
    return {
        leftP: rectArr.width / 2 + pos.leftP,
        topP: pos.topP,
    }
}
const updateSubMenu = (pos, data) => {
    store.hoverSubMenu.style.display = "inline-block";
    store.hoverSubMenu.innerHTML = data;
    store.hoverSubMenu.style.top = pos.topP + "px";
    store.hoverSubMenu.style.left = hoverSubMenuPosUtil(pos, data).leftP + "px";
}
const renderSubMenu = (pos, data) => {
    if (!store.hoverSubMenu) {
        let subMenu = document.createElement("div");
        subMenu.setAttribute("class", "hover-submenu");
        subMenu.setAttribute("id", "hover-submenu");
        store.hoverSubMenu = subMenu;
        store.navElement.appendChild(subMenu);
        updateSubMenu(pos, data);
    } else {
        updateSubMenu(pos, data);
    }
}

const dealTreeHover = (e, type) => {
    e.stopPropagation();
    try {
        let keyElement = getKeyEle(e.target, "li");
        // console.log(`hover:`, e.target.innerHTML, "-----", type)
        if (!type) {
            // console.log(keyElement);
            let bm = elePositionUtil(keyElement);
            renderSubMenu(bm, keyElement.innerHTML);
        } else {
            store.hoverSubMenu.style.display = "none";
        }
    } catch (e) {
    }
}


// 渲染导航栏
const renderNav = (data) => {
    renderTree(null, data.tree);
}

const backNav = () => {
    store.navStore = {}; // navStore 刷新。

    let lastNavData = store.navStack.pop();
    // console.log(JSON.stringify(lastNavData, null, 4))
    let data = Object.values(lastNavData);
    renderTree(null, data);
}

const register = (navElement, contentElement) => {
    store.navElement = navElement;
    store.contentElement = contentElement;
    store.navStack = new Stack();
    store.navStore = {}; // store nav tree.

    window.renderContent = renderContent;
    window.dealTreeClick = dealTreeClick;
    window.dealTreeHover = dealTreeHover;
    window.backNav = backNav;
}

export default {
    register,
    renderNav,
}